﻿using Microsoft.Win32;
using Newtonsoft.Json;
using NPOI.SS.Formula.Functions;
using NPOI.SS.UserModel;
using NPOI.XSSF.UserModel;
using Prism.Events;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Data;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using 基于WPF的电缆采样数据分析系统.Converters;
using 基于WPF的电缆采样数据分析系统.Models.Dbs;
using 基于WPF的电缆采样数据分析系统.Models.Dbs.DbService;
using 基于WPF的电缆采样数据分析系统.Models.Enums;
using 基于WPF的电缆采样数据分析系统.Models.ExportFormat;
using 基于WPF的电缆采样数据分析系统.Models.FileLogs;
using 基于WPF的电缆采样数据分析系统.Models.Task;
using 基于WPF的电缆采样数据分析系统.MsgEvents;
using 基于WPF的电缆采样数据分析系统.MsgEvents.AccountingReport;
using 基于WPF的电缆采样数据分析系统.MsgEvents.HistoricalData;
using 基于WPF的电缆采样数据分析系统.Tools.LangugeTool;
using 基于WPF的电缆采样数据分析系统.Tools.MessagePopupTool;

namespace 基于WPF的电缆采样数据分析系统.Tools.LogTools
{
    /// <summary>
    /// 全局日志工具
    /// </summary>
    public class GlobalLogTool
    {
        /// <summary>
        /// 发布订阅
        /// </summary>
        private readonly IEventAggregator Aggregator;

        /// <summary>
        /// 单例
        /// </summary>
        public static GlobalLogTool Instance = new GlobalLogTool();

        /// <summary>
        /// 构造器
        /// </summary>
        public GlobalLogTool()
        {
            Aggregator = App.GetService<IEventAggregator>();
            
        }


        /// <summary>
        /// 添加日志信息
        /// </summary>
        /// <param name="Uid">用户</param>
        /// <param name="OperateDescription">操作信息</param>
        public void AddLogToTDRWork(int Uid, string OperateDescription)
        {
            AllUsedLog allUsedLog = new AllUsedLog();

            // 日志id
            allUsedLog.Aid = GlobalVariableEdit.UsedLogList.Count + 1;

            // 用户
            allUsedLog.Uid = Uid;

            // 日志时间
            allUsedLog.Time = DateTime.Now;

            // 日志描述
            allUsedLog.OperateDescription = OperateDescription;

            // 日志是否选中
            allUsedLog.IsSelected = false;


            // 添加日志到全局环境中
            GlobalVariableEdit.UsedLogList.Add(allUsedLog);

            // 日志滚动到最后一行
            Aggregator.GetEvent<MsgScrollToTheLastLine>().Publish();

            // 添加操作日志
            AllUsedLogDAOService.Instance.AddAllUsedLogDAO(GetAllUsedLogDAO(allUsedLog));

            // 更新历史数据区
            Aggregator.GetEvent<MsgHistoricalOperationLogsAreRecorded>().Publish();
        }

        /// <summary>
        /// 获取DAO的操作日志
        /// </summary>
        /// <param name="allUsedLog"></param>
        /// <returns></returns>
        public AllUsedLogDAO GetAllUsedLogDAO(AllUsedLog allUsedLog)
        {
            AllUsedLogDAO allUsedLogDAO = new AllUsedLogDAO();
            allUsedLogDAO.Uid = allUsedLog.Uid;
            allUsedLogDAO.Time = allUsedLog.Time;
            allUsedLogDAO.OperateDescription = allUsedLog.OperateDescription;

            return allUsedLogDAO;
        }



        /// <summary>
        /// 导出显示列日志到表格
        /// </summary>
        /// <param name="UsedLogList"></param>
        /// <returns></returns>
        public RetResult ExportTheDisplayColumnLogsToTheTable(ObservableCollection<AllUsedLog> UsedLogList)
        {
            try
            {
                SaveFileDialog saveFileDialog = new SaveFileDialog();

                // 设置标题
                saveFileDialog.Title = LangugeConvertor.GetValue("ExportTheDisplayColumnLogsToTheTable");

                // 设置过滤器
                saveFileDialog.Filter = $"XLSX {LangugeConvertor.GetValue("File")} (*.xlsx)|*.xlsx";

                // 设置默认扩展名
                saveFileDialog.DefaultExt = "xlsx";

                // 设置默认文件名
                saveFileDialog.FileName = LangugeConvertor.GetValue("ExportingLogFiles") + DateTime.Now.ToString("yyyyMMddHHmmss");

                if (saveFileDialog.ShowDialog() == true)
                {
                    string selectedFilePath = saveFileDialog.FileName;

                    ObservableCollection<AllUsedLog> logsFormat = ExportTheDisplayColumnLogsToTheTableFormat(UsedLogList);

                    WriteExcel(logsFormat, selectedFilePath);

                    // 赋值日志文件的文件名
                    string[] newStr = selectedFilePath.Split("\\");

                    // 添加使用过文件的日志到集合中
                    FileTypeLog.AddUsedFileLogToList(FileType.ExportLog, newStr[newStr.Length - 1], LangugeConvertor.GetValue("ExportingLogFiles"), GlobalVariableEdit.CurrentUserInfo.Uid);


                    // 更新操作日志
                    AddLogToTDRWork(GlobalVariableEdit.CurrentUserInfo.Uid, LangugeConvertor.GetValue("ExportingLogFiles") + ": 【" + newStr[newStr.Length - 1] + "】");

                    return RetResult.Success;
                }

                return RetResult.Fail;

            }
            catch (Exception e)
            {
                MessagePopup.DisplayMessagePopup(LangugeConvertor.GetValue("CauseOfError") + e.Message);
                return RetResult.Fail;
            }
        }


        private ObservableCollection<AllUsedLog> ExportTheDisplayColumnLogsToTheTableFormat(ObservableCollection<AllUsedLog> UsedLogList)
        {
            ObservableCollection<AllUsedLog> newUsedLogList = new ObservableCollection<AllUsedLog>();

            for (int i = 0; i < UsedLogList.Count; i++)
            {
                newUsedLogList.Add(new AllUsedLog()
                {
                    Aid = UsedLogList[i].Aid,
                    Uid = UsedLogList[i].Uid,
                    Time = UsedLogList[i].Time,
                    OperateDescription = UsedLogList[i].OperateDescription,
                });
            }

            return newUsedLogList;
        }

        /// <summary>
        /// 写Excel文件
        /// </summary>
        /// <param name="CurrentTaskList"></param>
        /// <param name="SelectedFilePath"></param>
        private void WriteExcel(ObservableCollection<AllUsedLog> UsedLogList, string SelectedFilePath)
        {

            // Lets converts our object data to Datatable for a simplified logic.
            // Datatable is most easy way to deal with complex datatypes for easy reading and formatting.

            DataTable table = (DataTable)JsonConvert.DeserializeObject(JsonConvert.SerializeObject(UsedLogList), (typeof(DataTable)));
            var memoryStream = new MemoryStream();

            using (var fs = new FileStream(SelectedFilePath, FileMode.Create, FileAccess.Write))
            {
                IWorkbook workbook = new XSSFWorkbook();
                ISheet excelSheet = workbook.CreateSheet("Sheet1");

                List<String> columns = new List<string>();
                IRow row = excelSheet.CreateRow(0);
                int columnIndex = 0;

                foreach (System.Data.DataColumn column in table.Columns)
                {
                    columns.Add(column.ColumnName);
                    row.CreateCell(columnIndex).SetCellValue(column.ColumnName);
                    columnIndex++;
                }

                int rowIndex = 1;
                foreach (DataRow dsrow in table.Rows)
                {
                    row = excelSheet.CreateRow(rowIndex);
                    int cellIndex = 0;
                    foreach (String col in columns)
                    {
                        row.CreateCell(cellIndex).SetCellValue(dsrow[col].ToString());
                        cellIndex++;
                    }

                    rowIndex++;
                }
                workbook.Write(fs);
            }

        }
    }
}
